<template>
  <div class="contract-edit">
    <div class="flex-x contract-edit-title">
      <div class="flex-1 header__left"> {{ headTitle }}</div>
      <FormCellChange class="mar-r-8" :count="formCellCount" @update="(e)=>{formCellCount=e}"></FormCellChange>
      <div>
        <el-button type="plain-third" @click="goBack"
          >{{$t('common.base.back')}}</el-button
        >
        <el-button
          class="ml_12"
          type="plain-third"
          v-if="isShowTemporaryBtn"
          :disabled="isSaveLoading"
          @click="handleSave"
          >{{$t('common.base.temporaryStorage')}}</el-button
        >
        <el-button
          type="primary"
          @click="handleSubmit"
          :disabled="isSubmitLoading"
          >{{$t('common.base.save')}}</el-button
        >
      </div>
    </div>
    

    <div class="contract-edit-form bbx-cell-form-builder" :class="[formCellCount > 1 ? 'bbx-normal-form-builder-cell' : '']" v-loading.fullscreen.lock="showLoading">
      <form-builder
        v-if="fields.length && !showLoading"
        ref="formRef"
        :fields="fields"
        :value="form"
        mode="contract"
        :form-cell-count="formCellCount"
        @update="update"
        :formEditingMode="formEditingMode"
        @getDeleteFiles="getDeleteFiles"
      >
        <!-- 合同模板 -->
        <template slot="templateName" slot-scope="{ field }">
          <form-item class="bbx-form-cell-item" :label="field.displayName">
            <el-select 
              v-model="contractTemplateId" 
              :disabled="disabledTemplateName"
              :placeholder="$t('contract.setting.contractTemplate.pleaseSelectContractTemplate')" 
              :style="{width: '100%'}"
              @change="changeContractTemplate">
              <el-option
                v-for="item in contractTemplate"
                :key="item.id"
                :label="item.templateName"
                :value="item.id"
              />
            </el-select>
          </form-item>
        </template>
        
        <template slot="customer" slot-scope="{ field }">
          <form-item class="bbx-form-cell-item" :label="field.displayName">
            <biz-search-customer-select
              :field="customerField"
              :value="form.customer"
              :placeholder="$t('common.placeholder.searchCustomer')"
              :remote-method="remoteMethod"
              @input="updateCustomer"
            >
            </biz-search-customer-select>
          </form-item>
        </template>

        <template slot="tags" slot-scope="{ field }">
          <form-item class="bbx-form-cell-item" :label="field.displayName">
            <customer-tags :field="field" :value="form.tags" />
          </form-item>
        </template>

        <!-- 生效日期 -->
        <template slot="effectiveTime" slot-scope="{ field }">
          <form-item class="bbx-form-cell-item" :label="field.displayName">
            <form-date
              :field="field"
              :value="form.effectiveTime"
              @input="updateEffectiveTime"
              :disabledDate="
                time => pickerEffectiveTimeOptions(time, form.invalidTime)
              "
            ></form-date>
          </form-item>
        </template>

        <!-- 合同金额 -->
        <template slot="contractAmount" slot-scope="{ field, value }">
          <form-item class="bbx-form-cell-item" :label="field.displayName" :validation="validationContractAmount">
            <div class="form-item-price" :style="{ display: 'flex' }">
              <form-number
                :field="field"
                :value="form.contractAmount"
                :style="{ flex: 1 }"
                @input="updateContractAmount"
              ></form-number>
              <form-currency-type 
                class="contract-price"
                v-if="internationalGray"
                :value="form.contractAmountCurrency"
                @input="e => currencyHandleChange(e, field.fieldName + currencySuffix)"
              ></form-currency-type>
              <el-tooltip
                v-if="isShowCalculateBtn(field)"
                :content="$t('contract.edit.autoCalcTip')"
                placement="top"
              >
                <el-button
                  type="primary"
                  @click="handleClickAutoCalculation(field)"
                  class="ml_12"
                  >{{$t('contract.edit.autoCalc')}}</el-button
                >
              </el-tooltip>
            </div>
          </form-item>
        </template>

        <!-- 失效日期 -->
        <template slot="invalidTime" slot-scope="{ field }">
          <form-item class="bbx-form-cell-item" :label="field.displayName">
            <form-date
              :field="field"
              :value="form.invalidTime"
              @input="updateInvalidTime"
              :disabledDate="
                time => pickerInvalidTimeOptions(time, form.effectiveTime)
              "
            ></form-date>
          </form-item>
        </template>

        <!-- 金额相关字段 -->
        <template v-for="item in includePrice" :slot="item" slot-scope="{ field }">
          <form-item class="bbx-form-cell-item" :label="field.displayName">
            <div class="form-item-price">
              <form-number :field="field" :value="form[item]" @update="e => update(e)"></form-number>
              <form-currency-type 
                v-if="internationalGray"
                :value="form[field.fieldName + currencySuffix]"
                @input="e => currencyHandleChange(e, item + currencySuffix)"
              ></form-currency-type>
            </div>
          </form-item>
        </template>
      </form-builder>
    </div>

    <!-- 质保更新弹框 -->
    <warranty-interest-dialog
      ref="dialogRef"
      :dataList="productArr"
      :isCreateOrEffect="isCreateOrEffect"
      @handleUpdateQualityTime="handleUpdateQualityTime"
    ></warranty-interest-dialog>

    <!-- start 新建产品弹窗 -->
    <base-modal :title="$t('task.edit.createSth', {name: $t('common.base.product')})" :show.sync="addProductDialog" class="add-dialog-container" width="800px">
      <div id="createProductView"></div>
      <div class="dialog-footer" slot="footer">
        <el-button @click="addProductDialog = false">{{$t('common.base.close')}}</el-button>
        <el-button type="primary" @click="addProductSubmit">{{$t('common.base.save')}}</el-button>
      </div>
    </base-modal>
    <!-- end 新建产品弹窗 -->
  </div>
</template>
<script>
import i18n from '@src/locales';
import appConfig from 'app.config';

/* util */
import qs from '@src/util/querystring';
import { fmt_form_date } from '@src/filter/form.js';
import { isEmpty } from '@src/util/type';

// util
import { customerAddressSelectConversion } from '@src/util/conversionFunctionUtil.ts';

import WarrantyInterestDialog from '@src/modules/contract/components/WarrantyInterestDialog.vue';
import FormCellChange from '@src/component/compomentV2/FormCellChange/index.vue'

import {
  packToContract,
  packToForm,
  pickerEffectiveTimeOptions,
  pickerInvalidTimeOptions,
} from '../util/index';

import {
  toRefs,
  reactive,
  onMounted,
  ref,
  set,
  computed,
  provide,
  nextTick,
  onBeforeUnmount,
  getCurrentInstance
} from 'vue';
import { Message, Notification } from 'element-ui';

import platform from '@src/platform';
// api
import { getTaskDefaultInfo, getCreateProductData } from '@src/api/TaskApi.ts';
import {
  contractFieldList,
  saveContractList,
  getContractDetail,
  updateContract,
  getContractTemplateDetail,
  getContractTemplateList
} from '@src/api/ContractApi';
import { getCustomerList } from '@src/api/CustomerApi'

import FormMixin from '@src/component/form/mixin/form';

import NP from 'number-precision';
import moment from 'moment';

import * as FormUtil from '@src/component/form/util';
import { PageRoutesTypeEnum } from 'pub-bbx-global/pageType/dist/enum/PageRoutesEnum'
import { openAccurateTab, toast, backToFromAccurateTab } from '@src/util/platform'

import { useFormTimezone } from 'pub-bbx-utils'
const { disposeFormSubmitTime } = useFormTimezone()

import { jumpContractEdit, jumpContractDetail } from '@src/modules/contract/util/JumpContractUtil.js';

import { options } from '@src/modules/contract/contractList/fields.js';
import { CURRENCY_SUFFIX, contractAmountFieldNameList } from '@src/util/currency';
// 国际化灰度
import useFormMultiLanguage from '@hooks/useFormMultiLanguage'
const { internationalGray } = useFormMultiLanguage();
/* components */
import FormCurrencyType from '@src/component/form/components/FormCurrencyType/FormCurrencyType.vue';
import EventBus from '@src/util/eventBus';
import render from '@src/modules/task/edit/components/TaskEditForm/methods/render.js'
import { cloneDeep } from 'lodash'


export default {
  setup(props, context) {
    const dialogRef = ref(null);
    const tableData = ref([]);
    const formRef = ref(null);
    const addProductDialog = ref(false)
    const { proxy: currentCtx } = getCurrentInstance() || {};

    // 高级设置配置
    const settingConfig = ref({ productSupportCreate: false })
    const formCellCount = ref(1)

    const state = reactive({
      fields: [], // 表单字段
      form: {
        effectiveTime: '',
        invalidTime: '',
        tags: [],
        otherAmount: '0',
        discountAmount: '0',
        contractAmount: '0',
        quotationAmount: '0',
        procureAmount: '0'
      }, // 表单数据
      isSubmitLoading: false,
      isSaveLoading: false,
      currentCustomer: {
        id: '',
      },
      showLoading: false,
      productField: {},
      contractTemplate: [],
      contractTemplateId: '',
      productArr: [],
      minUpdateValue: '',
      maxUpdateValue: '',
      warrantyRightsDataList: [], // 更新质保服务传给后端的值
      needServerDeleFiles: []
    });


    const autoContractAmount = () => {
      let productVal = state.form[state.productField?.fieldName];
      
      if (!Array.isArray(productVal) || !productVal || !productVal.length) {
        let ret = NP.minus(state.form.otherAmount, state.form.discountAmount);
        return ret + '';
      } else {
        let ret = 0;
        let totalServiceAmount = 0; // 总服务金额

        let arr = productVal.map(item => {
          return item.serviceMoney;
        });

        totalServiceAmount = arr.reduce(function (prev, next) {
          return NP.plus(prev, next);
        }, 0);

        ret = NP.minus(
          NP.plus(totalServiceAmount, state.form.otherAmount),
          state.form.discountAmount
        );
        return ret + '';
      }
    };

    const action = computed(() => {
      return location.pathname.indexOf('/contract/create') >= 0 ? 'create' : 'edit';
    });
    const actionText = computed(() => {
      return action.value === 'create' ? i18n.t('common.base.create') : i18n.t('common.base.edit');
    });
    const formEditingMode = computed(() => {
      return action.value === 'create' ? 'create' : 'edit'
    })
    // 判断新建编辑
    const isCreate = computed(() => {
      return action.value === 'create';
    });
    // 编辑
    const isEdit = computed(() => {
      return action.value === 'edit';
    });
    // 是否禁用合同模板
    const disabledTemplateName = computed(() => {
      return Boolean(isEdit.value) || false
    })
    // 获取搜索参数
    const searchQuery = computed(() => {
      return qs.parse(window.location.search);
    })
    // 是否显示暂存按钮
    const isShowTemporaryBtn = computed(() => {
      return isCreate.value || searchQuery.value?.source;
    });
    // 标题
    const headTitle = computed(() => {
      // 新建、草稿 - 新建合同
      // 编辑 - 编辑合同
      return isShowTemporaryBtn.value ? i18n.t('common.pageTitle.pageContractCreate') : i18n.t('common.pageTitle.pageContractEdit');
    }); 
    // 合同id
    const getContractId = computed(() => {
      return location.pathname.split('/contract/edit/')[1] || '';
    });

    // 产品质保高级设置
    const proQualityInfo = computed(() => {
      return settingConfig.value?.proQualityInfo || {}
    })

    // 新建产品的权限
    const createdProductPermission = computed(()=> {
      let initData = JSON.parse(sessionStorage.getItem('_init_data'));
      return initData?.auths?.PRODUCT_CREATE > 0;
    })

    // 新建产品的Form的Dom
    const productFormViewDom = computed(()=> {
      return currentCtx?.productFormView?.$refs?.ProductCreateView || {};
    })

    // 产品质保是否开启 && 按合同中产品服务时间字段 PRODUCT_SERVICE_DATE
    const proQualitySwitch = computed(() => {
      return proQualityInfo.value.productQualitySwitch && proQualityInfo.value.productQualityCondition2 === 'PRODUCT_SERVICE_DATE'
    })

    // 产品质保是否开启 && 按合同中产品服务时间字段 PRODUCT_SERVICE_PROJECT 
    const proQualityServiceProject = computed(() => {
      return proQualityInfo.value.productQualitySwitch && proQualityInfo.value.productQualityCondition2 === 'PRODUCT_SERVICE_PROJECT'
    })

    // 合同创建 还是 合同生效
    const isCreateOrEffect = computed(() => {
      const result = (options || []).find(item => item.value === proQualityInfo.value.productQualityCondition1)
      return result?.label || '';
    })

    // 计划任务是否开启
    const planTaskSwitch = computed(() => {
      return settingConfig.value?.planTask?.triggerPlanTaskSwitch || false
    })

    // 计划任务编号
    const planTaskNumber = computed(() => {
      return settingConfig.value?.planTask?.triggerPlanTaskCondition || false
    })

    // =================== 客户
    const customerField = computed(
      () => state.fields.filter(f => f.fieldName === 'customer')[0]
    );

    /** 搜索客户 */
    const remoteMethod = async params => {
      return await getCustomerList(params)
        .then(res => {
          if (!res || !res.list) return;

          res.list = res.list.map(customer =>
            Object.freeze({
              label: customer.name,
              value: customer.id,
              ...customer,
            })
          );
          return res;
        })
        .catch(e => console.error(e));
    };

    /**
     * @description 获取Field
     */
    const getField = type => {
      let field = state.fields.filter(item => item.formType == type)[0];
      return field;
    };

    /** 更新客户 */
    const updateCustomer = async value => {
      let selectedCustomer = value?.[0] || {};
      let currentCustomerId = state.currentCustomer?.id;
      let selectedCustomerId =
        selectedCustomer?.id || selectedCustomer?.value || '';

      // 更新客户数据
      update({
        field: getField('customer'),
        newValue: [
          {
            id: selectedCustomer.id,
            value: selectedCustomer.id,
            label: selectedCustomer.name,
          },
        ],
      });

      // 判断选中的客户是否与当前客户数据一致
      if (currentCustomerId === selectedCustomerId) return;

      try {
        const result = await getTaskDefaultInfo({
          customerId: selectedCustomerId,
        });

        state.currentCustomer.id = selectedCustomerId;

        let { linkman, address } = result;

        // 重置联系人和地址和产品
        update({ field: getField('linkman'), newValue: [] });
        update({ field: getField('customerAddress'), newValue: [] });
        update({ field: getField('product'), newValue: [] });

        // 绑定联系人和地址
        linkman && bindLinkman(linkman);
        address && bindAddress(address);
      } catch (error) {
        console.warn('task-edit-form: updateCustomer -> error', error);
      }
    };

    /**
     * @description 绑定地址
     * @param {Object} address 地址数据
     */
    const bindAddress = (address = {}) => {
      let field = getField('customerAddress');
      let value = [
        customerAddressSelectConversion({...address}),
      ];
      update({ field: { fieldName: field?.fieldName }, newValue: value });
    };

    /**
     * @description 绑定联系人
     * @param {Object} linkman 联系人数据
     */
    const bindLinkman = (linkman = {}) => {
      let field = getField('linkman');
      let value = [
        {
          id: linkman.id,
          name: linkman.name,
          phone: linkman.phone,
        },
      ];
      update({ field: { fieldName: field?.fieldName }, newValue: value });
    };

    // 客户================E

    // 获取表单字段
    const fetchFields = async () => {
      state.showLoading = true;
      try {
        let ret = await contractFieldList({
          templateId: state.contractTemplateId
        });
        if (ret.success) {
          state.fields = JSON.parse(JSON.stringify(ret.result));
        } else {
          state.fields = [];
        }

        if (isEdit.value) {
          fetchContractList();
        } else {
          state.form = FormUtil.initialize(state.fields, {});
        }

        state.productField = getField('product');
      } catch (err) {
        console.log('error => fetchFields', err);
      } finally {
        state.showLoading = false;
      }
    };

    // 获取详情数据
    const fetchContractList = () => {
      getContractDetail({
        contractId: getContractId.value,
      }).then(async res => {
        if (res.success) {
          let { productList, sparepartList, productWarrantyList } = res.result || {}
          
          let formType = ['product', 'subSparePart', 'productWarrantyService']

          let obj = {
            product: productList,
            subSparePart: sparepartList,
            productWarrantyService: productWarrantyList
          }
          
          formType.forEach(item => {
            let fieldName = getField(item)?.fieldName || '';
            res.result.attribute[fieldName] = obj[item]
          })

          // 处理富文本
          res.result = await FormUtil.initRichTextContent(state.fields, res.result);

          let ret = packToForm(res.result);

          state.form = FormUtil.initialize(state.fields, ret);
        } else {
          Message({
            message: res.message,
            type: 'error',
          });
        }
      });
    };

    /* form-builder更新事件 */
    const update = ({ field, newValue, oldValue }) => {
      let { fieldName = '', displayName = '' } = field || {};
      if (appConfig.debug) {
        console.info(
          `[FormBuilder] => ${displayName}(${fieldName}) : ${JSON.stringify(
            newValue
          )}`
        );
      }
      set(state.form, fieldName, newValue);
    };

    // 刷新tab
    const reloadTab = () => {
      let fromId = window.frameElement.getAttribute('fromid');
      platform.refreshTab(fromId);
    };

    // 点击跳转工单计划任务
    const jumpTaskPlan = (contractId) => {
      let fromId = window.frameElement.getAttribute('id');

      openAccurateTab({
        type: PageRoutesTypeEnum.PagePlanTaskCreate,
        params: `defaultTypeId=${planTaskNumber.value}&contractId=${contractId}`,
        fromId,
      })
    };
    // 返回
    const goBack = () => {
      let id = window?.frameElement?.dataset?.id;
      platform.closeTab(id);

      if (isEdit.value) {
        jumpContractDetail({id: getContractId.value, templateId: state.contractTemplateId })
      } else {
        openAccurateTab({
          type: PageRoutesTypeEnum.PageContractList,
          reload: true,
        });
      }
    };

    // 保存合同
    const saveContract = isTemporary => {
      // 处理国际化日期时间数据转换
      const submitForm = disposeFormSubmitTime(state.fields, state.form)
      let params =
        packToContract(
          state.fields,
          submitForm,
          isTemporary,
          proQualitySwitch.value
        ) || {};

      if (formEditingMode.value == 'edit' && state.needServerDeleFiles.length) {
        params['deleteFiles'] = state.needServerDeleFiles
      }
      
      let fn = isCreate.value ? saveContractList : updateContract;
      fn({
        ...params,
        isTemporary,
        id: Number(getContractId.value),
        templateId: state.contractTemplateId,
        warrantyRightsDataList: isTemporary ? [] : state.warrantyRightsDataList
      })
        .then(res => {
          if (res.success) {
            let text = isTemporary ? i18n.t('common.base.temporaryStorage') : actionText.value;
            Notification({
              title: i18n.t('common.base.toast'),
              message: i18n.t('common.base.success'),
              type: 'success',
            });


            let contractId = isCreate.value ? res.result.id : getContractId.value;

            let id = window?.frameElement?.dataset?.id;

            platform.closeTab(id);
            // 暂存
            if (isTemporary) {
              jumpContractEdit({ id: contractId, ...res.result})
              return
            }
            
            // 开启就跳转到计划任务
            if (planTaskSwitch.value) {
              jumpTaskPlan(contractId)
              return
            }

            jumpContractDetail({ id: contractId, ...res.result})
          } else {
            Message({
              message: res.message,
              type: 'error'
            });
          }
        })
        .finally(() => {
          state.isSaveLoading = false;
          state.isSubmitLoading = false;
        });
    };
    // 暂存
    const handleSave = () => {
      state.isSaveLoading = true;
      saveContract(true);
    };
    // 获取系统产品质保服务
    const fetchSystemProductWarray = () => {
      const productWarrayField = getField('productWarrantyService') || {};
      const productWarrayInfo = state.form[productWarrayField?.fieldName] || [];

      let newSystemArrs = productWarrayInfo.filter(item => item.system)

      return newSystemArrs || [];
    }
    // 获取产品质保服务列表数据
    const fetchProductWarrayServiceList = () => {
      const systemList = fetchSystemProductWarray()
      
      if(!systemList) return;

      // 存储维保延保服务时间
      let serviceTimeArr = []

      systemList.forEach(item => {
        serviceTimeArr.push(item.svcStartTime, item.svcEndTime)
      })

      let ret = serviceTimeArr.sort((a, b) => a - b)
      
      // extendService 延保 maintainService 维保

      state.minUpdateValue = fmt_form_date(ret[0])
      state.maxUpdateValue = fmt_form_date(ret[serviceTimeArr.length - 1])
    }

    // 质保开始时间修改后的取值：
    // 质保开始时间为空取最小值，不为空取质保开始时间；
    const modifiedValueStartDate = (qualityInfo) => {
      return qualityInfo?.qualityInfoStartTime || state.minUpdateValue;
    }
    // 质保结束时间修改后的取值：
    // 取维保延保组合时间的最大值。如果比质保开始时间修改后的值小，取质保结束时间。
    const modifiedValueEndDate = (qualityInfo) => {      
      let qualityStartTime = moment(modifiedValueStartDate(qualityInfo)).valueOf(); // 质保开始更新后的值
      let maxTime = moment(state.maxUpdateValue).valueOf(); // 转时间戳

      return maxTime > qualityStartTime ? state.maxUpdateValue : qualityInfo?.qualityInfoEndTime;
    }
    // 获取质保服务更新提示弹框列表
    const fetchWarrantyServiceUpdateList = (productInfo) => {
      state.productArr = [];

      (productInfo || []).map(item => {
        state.productArr.push({
          productId: item?.id || '',
          serialNumber: item?.serialNumber || '',
          name: item?.name || '',
          updateText: i18n.t('common.form.preview.qualityInfo.qualityStartDate'),
          beforeValue: item?.qualityInfoStartTime || '',
          afterValue: modifiedValueStartDate(item)
        }, {
          productId: item?.id || '',
          serialNumber: item?.serialNumber || '',
          name: item?.name || '',
          updateText: i18n.t('common.form.preview.qualityInfo.qualityEndDate'),
          beforeValue: item?.qualityInfoEndTime || '',
          afterValue: modifiedValueEndDate(item)
        })

        return state.productArr;
      })
    }

    // 是否显示更新质保弹框
    const isShowUpdateQualityDialog = () => {
      let productInfo = state.form[state.productField?.fieldName] || [];

      let productWarrayInfo = fetchSystemProductWarray()
      fetchProductWarrayServiceList()

      // 产品列表有值 & 产品质保服务列表有值 & proQualityServiceProject为true 显示弹框
      if(productInfo.length && productWarrayInfo.length && proQualityServiceProject.value) {
        fetchWarrantyServiceUpdateList(productInfo)
        dialogRef.value.visible = true;
      } else {
        // 不显示弹框
        state.warrantyRightsDataList = []
        state.isSubmitLoading = true;
        saveContract(false);
      }
    }

    // 更新质保时间
    const handleUpdateQualityTime = (isUpdate) => {
      if(isUpdate) {
        state.warrantyRightsDataList = state.productArr.map(item => {
          return {
            productId: item?.productId || '',
            productNo: item?.serialNumber || '',
            productName: item?.name || '',
            updateField: item?.updateText || '',
            oldValue: item?.beforeValue || '',
            newValue: item?.afterValue || ''
          }
        })
      } else {
        state.warrantyRightsDataList = []
      }

      state.isSubmitLoading = true;
      saveContract(false);
    }
    // 提交
    const handleSubmit = () => {
      try {
        formRef.value.validate(false).then(valid => {
          if (!valid) return false;

          isShowUpdateQualityDialog()
        });
      } catch (err) {
      } finally {
        state.isSubmitLoading = false;
      }
    };

    provide('configData', settingConfig);

    //获取设置信息
    const getConfigData = () => {
      getContractTemplateDetail({
        id: state.contractTemplateId
      })
        .then(res => {
          const { success, result, message } = res;

          if (!success) return toast(message, 'error');

          settingConfig.value = { ...settingConfig.value, ...(result?.setting || {}) };
        })
        .catch(err => {
          console.log(err);
        });
    };

    // 更新生效日期
    const updateEffectiveTime = val => {
      state.form.effectiveTime = val;
    };

    // 更新失效日期
    const updateInvalidTime = val => {
      state.form.invalidTime = val;
    };

    // 更新合同金额
    const updateContractAmount = val => {
      state.form.contractAmount = val;
    };

    // 点击自动计算
    const handleClickAutoCalculation = () => {
      state.form.contractAmount = autoContractAmount();
    };

    // 获取合同模板下拉框数据
    const fetchContractTemplate = async() => {
      try {
        let ret = await getContractTemplateList();

        const { success, message, result } = ret || {};

        if (!success) return toast(message, 'error');

        state.contractTemplate = (result || []).filter(item => item.enabled);
      } catch (err) {
        console.log('error => fetchContractTemplate', err);
      }
    }

    // change 合同模板
    const changeContractTemplate = (val) => {
      state.contractTemplateId = val;
      
      fetchFields()
    }

    /* ----------币种相关 start---------- */
    // 金额字段
    const includePrice = contractAmountFieldNameList.filter(x => x !== 'contractAmount');

    const currencySuffix = computed(() => {
      return CURRENCY_SUFFIX;
    })

    // 货币选择变化
    const currencyHandleChange = (val, fieldName) => {
      update({ field: { fieldName }, newValue: val });

      nextTick(() => {
        // 如果存在计算公式涉及当前金额字段，切换币种时需要重新触发币种是否统一的校验 || 合同金额存在也效验
        let isNeedValidate = false;
        let formulaFields = (state?.fields || []).filter(item => item.formType === 'formula');
        const isContractAmount = (state?.fields || []).find(item => item.fieldName === 'contractAmount');
        
        // 判断所有的计算公式是否关联当前的金额字段
        isNeedValidate = formulaFields && formulaFields.some(item => {
          return !isEmpty(item.setting.formula) && item.setting.formula.some(f => !f.isOperator && contractAmountFieldNameList.includes(f.value));
        });

        if(isNeedValidate || isContractAmount !== -1) formRef.value.validate();
      })
    }

    // 获取产品的表单相id
    const productFieldName = computed(() => {
      const { fieldName } = state.fields.find(x => x.formType === "product");
      return fieldName;
    })


    // 效验合同金额的币种是否和当前需要计算的金额币种不同
    const isCurrencyNotAlike = (field) => {
      let currencyList = [];
      const contractCurrency = state.form[field.fieldName + currencySuffix.value];
      
      try {
        const productCurrencyList = state.form[productFieldName.value]?.map(x => x.serviceMoneyCurrency || 'CNY');
        const amountCurrencyList = includePrice.map(x => state.form[x + currencySuffix.value]).filter(Boolean);
        currencyList = productCurrencyList.concat(amountCurrencyList);
      }catch(e) {
        console.log('validationContractAmount: ', e);
      }
      
      return currencyList.some(x => x !== contractCurrency);
    }
    // 合同金额校验 相加的币种是否相同
    const validationContractAmount = (value, field) => {
      return new Promise((resolve, reject) => {
        if(isCurrencyNotAlike(field) && internationalGray && field.setting?.checkCurrency){
          return resolve(i18n.t('common.util.validator.currencyCheckTip'));
        }

        resolve(null);
      })
    }
    /* ----------币种相关 end---------- */


    /* ---------新建产品相关 start -------- */
    createdProductPermission.value && (settingConfig.value.productSupportCreate = true)

    const fetchProductData = async ()=> {
      const ret = await getCreateProductData();

      const { status, message, data } = ret;

      let isSuccess = status == 0;
      if (isSuccess) {
        data.isContractCreate = true
        currentCtx.productInitData = data;
        currentCtx.productFormView = currentCtx.renderProductForm(data);
      } else {
        currentCtx.$platform.alert(message);
      }
      return data;
    }

    const addEventListenerAddProduct = ()=> {
      EventBus.$on('form-product-add', async()=> {

        if (!state.form['customer']?.[0]?.id) {
          currentCtx.$platform.alert(i18n.t('task.tip.pleaseChooseSth', {name: i18n.t('common.base.customer')}));
          return;
        }
        await fetchProductData()
        nextTick(()=> addProductDialog.value = true)
      })
    }

    const removeEventListenerAddProduct = ()=> {
      EventBus.$off('form-product-add', ()=> {})
    }


    const addProductSubmit = ()=> {
      let customer = {
        id: state.form['customer']?.[0]?.id,
        linkman: {id: state.form['linkman']?.[0]?.id},
      };
      const productFieldName = state.fields.find(item=> item.formType === 'product')?.fieldName
      const productDefaultValue = state.form?.[productFieldName] || []
      productFormViewDom.value.submit(customer, data => {
        let productArr = cloneDeep(productDefaultValue);
        productArr.push({
          value: data.productId,
          label: data.productName,
          id: data.productId,
          name: data.productName,
          customerId: customer.id,
          ...data,
        });

        if(productFieldName) {
          // 不需要添加值产品子表单
          // state.form[productFieldName] = [...state.form[productFieldName], ...productArr]
        }
        addProductDialog.value = false;
      });
    }

    /* ---------新建产品相关 end-------- */


    const isShowCalculateBtn = (field)=> {
      if(Reflect.has(field.setting, 'isCalculationDisplayed')) {
        return field.setting.isCalculationDisplayed
      } 
      return true
    }
    // 删除附件
    const getDeleteFiles = (files) => {
      state.needServerDeleFiles = [...state.needServerDeleFiles, ...files]
    }

    onMounted(async () => {
      let query = qs.parse(window.location.search);
      if (query?.source) {
        let id = window.frameElement.dataset.id;
        platform.setTabTitle({
          id,
          title: i18n.t('contract.edit.frameTabTitle'),
        });
      }

      await fetchContractTemplate(); 
      state.contractTemplateId = query?.contractTemplateId || '';

      await getConfigData();
      await fetchFields();

      

      addEventListenerAddProduct()
      
    });

    onBeforeUnmount(()=> {
      removeEventListenerAddProduct()
    }) 

    return {
      tableData,
      dialogRef,
      formRef,
      ...toRefs(state),
      update,
      fetchFields,
      goBack,
      handleSave,
      handleSubmit,
      remoteMethod,
      updateCustomer,
      customerField,
      updateEffectiveTime,
      updateInvalidTime,
      updateContractAmount,
      pickerEffectiveTimeOptions,
      pickerInvalidTimeOptions,
      handleClickAutoCalculation,
      searchQuery,
      isShowTemporaryBtn,
      changeContractTemplate,
      isCreateOrEffect,
      handleUpdateQualityTime,
      currencySuffix,
      internationalGray,
      includePrice,
      currencyHandleChange,
      validationContractAmount,
      addProductDialog,
      addProductSubmit,
      isShowCalculateBtn,
      formCellCount,
      headTitle,
      disabledTemplateName,
      formEditingMode,
      getDeleteFiles
    };
  },

  components: {
    'customer-tags': {
      name: 'customer-tags',
      mixins: [FormMixin],
      props: {
        field: {
          type: Object,
          default: () => ({}),
        },
        value: {
          type: Array,
          default: () => [],
        },
      },
      render(h) {
        return (
          <biz-team-select value={this.value} onInput={this.input} multiple />
        );
      },
      methods: {
        input(value) {
          this.$emit('input', {
            field: this.field,
            newValue: value,
            oldValue: [],
          });
        },
      },
    },
    WarrantyInterestDialog,
    [FormCurrencyType.name]: FormCurrencyType,
    FormCellChange,
  },

  methods: {
    ...render
  },
};
</script>
<style lang="scss">
.theme-default {
  padding: 12px;
}
</style>
<style lang="scss" scoped>
.contract-edit {
  min-width: 1100px;
  height: 100%;
  background: #fff;
  border-radius: 4px;
  display: flex;
  flex-flow: column nowrap;
  overflow: hidden;
  ::v-deep .bbx-cell-form-box-2.form-builder {
    padding:24px 32px !important;
  }
  &-title {
    padding: 12px;
    border-bottom: 1px solid #e8e8e8;
    justify-content: end !important;
    .header__left {
      font-weight: 500;
      color: #262626;
      font-size: 16px;
    }
  }
  &-form {
    flex: 1;
    overflow: auto;
    .form-builder {
      padding: 0;
      margin: 24px auto 10px;
      max-width: 700px;
    }
  }

  .form-item-price {
    display: flex;
    width: 100%;
    .form-number {
      width: 100%;
    }
    .form-text {
      width: 40%;
      margin-left: 6px;

      ::v-deep .el-select {
        width: 100%;
      }
    }

    .contract-price {
      width: 30%;
    }
  }
}
</style>